import axios from "axios"
import { Message as showMessage } from "element-ui"
import router from "../router"
import errorCode from "./errorCode"
// import store from "@/store"
import Qs from "qs"
// axios.defaults.headers["Content-Type"] = "application/json" //底下创建axios实例时配置了，这个不用重复配置，再说，这也是axios的默认配置
//过滤为空的参数
const cleanObject = object => {
  const result = { ...object }
  Object.keys(result).forEach(key => {
    const value = result[key]
    if (!value) {
      delete result[key]
    }
  })
  return result
}
// 对所有 axios 请求做处理
axios.defaults.withCredentials = true
axios.defaults.headers.common["Authorization"] = "" // 设置请求头为 Authorization
export default function request(options) {
  return new Promise((resolve, reject) => {
    // 创建axios实例
    const service = axios.create({
      // 表示请求URL公共部分，它会读取这里的值，然后拼接上页面使用的url
      baseURL: process.env.VUE_APP_baseUrl,
      timeout: 5000,
      withCredentials: false, // 跨域请求时是否需要cookie等凭证
      responseType: "json",
      params: {},
      maxContentLength: 2000,
      validateStatus: status => status >= 200 && status < 300, //默认值
      maxRedirects: 5, //最大允许重定向次数
      headers: {
        //公共请求头配置，本项目请求头大多数接口是这个，所以这里可以配置一下，对于特殊接口单独配置
        "Content-Type": "application/x-www-form-urlencoded; charset=UTF-8"
      }
      // transformRequest: [data => Qs.stringify(data, { indices: true })] //将参数key=value序列化，因为本项目有的接口需要json/对象传参数，这里就不能这样直接全局配置，否则有的接口会报400(因为你把json或者是对象类型的数据，在这里key=value序列化了)
    })
    // request拦截器
    service.interceptors.request.use(
      config => {
        switch (config.method) {
          case "get":
            if (!config.params) {
              config.params = {}
            } else {
              config.params = cleanObject(config.params)
            }
            break
          case "post":
            if (!config.data) {
              config.data = {}
            } else {
              config.data = cleanObject(config.data)
            }
            if (config.type === "keyValue") {
              config.data = Qs.stringify(config.data) //配套application/x-www-form-urlencoded使用
            } else {
              config.headers["Content-Type"] = "application/json"
            }
            break
          case "put":
            if (!config.params) {
              config.data = {}
            } else {
              config.data = cleanObject(config.data)
            }
            config.headers["Content-Type"] = "application/json"
            break
          case "delete":
            if (!config.params) {
              config.data = {}
            } else {
              config.params = cleanObject(config.params)
            }
            break
          default:
        }
        console.log(`【request】url:${config.url},data:${config.data} `)
        return config
      },
      error => {
        console.log(error)
        Promise.reject(error)
      }
    )

    // 响应拦截器
    service.interceptors.response.use(
      res => {
        // 未设置状态码则默认成功状态
        const code = parseInt(res.data.code) || 0
        // 获取错误信息
        const msg = res.data.msg || errorCode[code] || errorCode["default"]
        if (code == "3001") {
          showMessage({
            message: "已过期，请重新登录",
            type: "error"
          })
          reject(new Error(msg))
          router.push("/login")
        } else if (code != 0) {
          showMessage({
            message: msg,
            type: "error"
          })
          reject(new Error(msg))
          return
        } else {
          resolve(res.data) //获取到成功的响应了，就把结果resolve出去
        }
      },
      error => {
        console.log("err" + error)
        let { message } = error
        if (message == "Network Error") {
          message = "网络异常，请检查网络"
        } else if (message.includes("timeout")) {
          message = "系统接口请求超时，请检查网络"
        } else if (message.includes("Request failed with status code")) {
          message = "系统接口" + message.substr(message.length - 3) + "异常"
        }
        showMessage({
          message: message,
          type: "error",
          duration: 5 * 1000
        })
        return reject(error)
      }
    )
    service(options)
  })
}
